<template>
  <!-- 申请公司 -->
  <div v-waterMarker v-loading="queueLoading" class="merak-card merak-container-has-search" curPageName="ApplicantCompany">
    <SearchBar
      closePlan
      closeAdvanced
      :placeholder="$t('marking_company.search_placeholder')"
      @search-event="data => (tableState.params!.key_words = data.search)"
    >
      <template #header>
        <el-select
          v-model="searchValue.own"
          clearable
          :placeholder="$t('marking_company.is_own')"
          @change="value => (tableState.params!.is_own = value)"
        >
          <el-option :value="1" :label="$t('merak.yes')" />
          <el-option :value="0" :label="$t('merak.no')" />
        </el-select>
        <el-select
          v-model="searchValue.status"
          clearable
          :placeholder="$t('marking_company.status')"
          @change="value => (tableState.params!.status = value)"
        >
          <el-option :value="1" :label="$t('marking_company.enable')" />
          <el-option :value="0" :label="$t('marking_company.disable')" />
        </el-select>
      </template>
      <template #footer>
        <el-button
          v-auth="{ authArr: auth, key: 'add' }"
          type="primary"
          @click="Object.assign(addState, { type: 'add', data: { is_own: 1 }, visible: true })"
        >
          {{ $t("marking_company.add_company") }}
        </el-button>
      </template>
    </SearchBar>
    <div class="merak-table-wrapper">
      <MerakXTable
        ref="tableRef"
        v-bind="tableState"
        :loading="!!queueLoading ? false : undefined"
        :column-type="tableColumnType"
        :toolbar="tableToolbar"
        :enabled-export="!!auth?.export.show"
        :queryColumns="handleQueryColumns"
        :queryData="handleQueryData"
      >
        <template #custom-handler="{ row }">
          <el-button
            v-auth="{ authArr: auth, key: 'edit' }"
            type="primary"
            link
            @click="Object.assign(addState, { type: 'edit', data: { ...(row ?? {}) }, visible: true })"
          >
            {{ $t("merak.edit") }}
          </el-button>
          <el-button
            v-auth="{ authArr: auth, key: 'edit' }"
            link
            :type="!!row.status ? 'danger' : 'primary'"
            :disabled="!!row.disabled"
            @click="handleUpdateStatus(!!row.status, row)"
          >
            {{ !!row.status ? $t("marking_company.disable") : $t("marking_company.enable") }}
          </el-button>
          <el-button type="primary" link @click="Object.assign(gcpState, { data: { ...row }, visible: true })">
            {{ $t("marking_company.gcp_manage") }}
          </el-button>
        </template>
      </MerakXTable>
    </div>
    <el-drawer v-model="addState.visible" size="50%" destroy-on-close :title="drawerTitle" @closed="handleCloseAdd">
      <div class="tag-company-drawer">
        <div class="tag-company-drawer-content">
          <el-scrollbar>
            <el-form ref="formRef" labelPosition="top" :model="addState.data" :rules="addFormRules">
              <el-row :gutter="40">
                <el-col :span="12">
                  <el-form-item prop="import_company_name" :label="$t('marking_company.import_company_name')">
                    <el-input v-model="addState.data.import_company_name" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="short_name" :label="$t('marking_company.short_name')">
                    <el-input v-model="addState.data.short_name" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="inn" :label="$t('marking_company.inn')">
                    <el-input v-model="addState.data.inn" class="qf_input" :maxlength="20" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="contract_date" :label="$t('marking_company.contract_date')">
                    <el-date-picker
                      v-model="addState.data.contract_date"
                      class="qf_date"
                      value-format="YYYY-MM-DD"
                      :format="format"
                    />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="contract_number" :label="$t('marking_company.contract_number')">
                    <el-input v-model="addState.data.contract_number" class="qf_input" :maxlength="50" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="token" :label="$t('marking_company.token')">
                    <el-input v-model="addState.data.token" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="oms_id" :label="$t('marking_company.oms_id')">
                    <el-input v-model="addState.data.oms_id" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="contact_person" :label="$t('marking_company.contact_person')">
                    <el-input v-model="addState.data.contact_person" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="api_key_kmt" :label="$t('marking_company.api_key_kmt')">
                    <el-input v-model="addState.data.api_key_kmt" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="is_own" :label="$t('marking_company.is_own')">
                    <el-radio-group v-model="addState.data.is_own">
                      <el-radio :value="1" :label="$t('merak.yes')" />
                      <el-radio :value="0" :label="$t('merak.no')" />
                    </el-radio-group>
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="address" :label="$t('marking_company.address')">
                    <el-input v-model="addState.data.address" class="qf_input" :maxlength="200" />
                  </el-form-item>
                </el-col>
                <el-col :span="12">
                  <el-form-item prop="factory_ru_id" :label="$t('marking_company.factory_ru_id')">
                    <el-select
                      v-model="addState.data.factory_ru_id"
                      class="qf_select"
                      filterable
                      remote
                      :remote-method="handleRemoteMethod"
                      :placeholder="$t('marking_company.factory_ru_id_placeholder')"
                    >
                      <template v-if="!!addState.currentOptions.length">
                        <el-option v-for="option in addState.currentOptions" :value="option.value" :label="option.label" />
                      </template>
                      <el-option
                        v-else-if="!!factoryDefaultOption"
                        :value="factoryDefaultOption.value"
                        :label="factoryDefaultOption.label"
                      />
                    </el-select>
                  </el-form-item>
                </el-col>
              </el-row>
            </el-form>
          </el-scrollbar>
        </div>
        <div class="tag-company-drawer-footer">
          <el-button @click="addState.visible = false">{{ $t("merak.cancel") }}</el-button>
          <el-button
            v-if="addState.type === 'add'"
            type="primary"
            plain
            :loading="addState.resetLoading"
            @click="handleSave(true)"
          >
            {{ $t("merak.save_continue") }}
          </el-button>
          <el-button type="primary" :loading="addState.loading" @click="handleSave()">{{ $t("merak.save") }}</el-button>
        </div>
      </div>
    </el-drawer>
    <el-drawer
      v-model="gcpState.visible"
      size="50%"
      destroy-on-close
      :title="`${$t('marking_company.gcp_manage')} #${gcpState.data.short_name}`"
    >
      <GCP :visible="!!auth?.edit.show" :data="gcpState.data" />
    </el-drawer>
  </div>
</template>

<script setup lang="ts" name="ApplicantCompany">
import { getCurrentInstance, ref, reactive, computed, nextTick } from "vue";

import { useGlobalStore } from "@/stores/modules/global";

import useLoading from "@/hooks/useLoading";

import useDateFormat from "@/hooks/useDateFormat";

import {
  FormRules,
  ElButton,
  ElDrawer,
  ElForm,
  ElFormItem,
  ElRow,
  ElCol,
  ElScrollbar,
  ElInput,
  ElDatePicker,
  ElRadioGroup,
  ElRadio,
  ElSelect,
  ElOption,
  ElMessage
} from "element-plus";

import SearchBar from "@/components/SearchBar/index.vue";

import MerakXTable, { MerakXTableInstance, MerakXTableProps } from "@/components/MerakXTable";

import GCP from "./gcp.vue";

import { confirmWarningMsg } from "@/utils/messageUtils";

import { ResultEnum } from "@/enums/httpEnum";
import { Path, getTableColumns, getTableData } from "@/api/modules/table";
import { OptionType, saveCompany, updateStatus, validField, getFactoryOptions } from "@/api/modules/markingManagement/company";
import { UserAuthType, getUserAuth } from "@/api/modules/user";

const currentInstance = getCurrentInstance();

const { language } = useGlobalStore();

const { queueId, queueLoading } = useLoading(800);

const { format } = useDateFormat();

const tableRef = ref<MerakXTableInstance>();

const formRef = ref<InstanceType<typeof ElForm>>();

// 保存状态
const saved = ref(false);

// 页面权限
const auth = ref<UserAuthType>();

// 搜索赋值
const searchValue = reactive<{
  own?: any;
  status?: any;
}>({});

// 表格属性
const tableState = reactive<MerakXTableProps>({
  columnsByStore: [],
  rowKey: "import_company_id",
  params: {}
});

// 添加弹窗相关数据
const addState = reactive<{
  type?: "add" | "edit";
  data: Record<string, any>;
  options: OptionType[];
  currentOptions: OptionType[];
  visible: boolean;
  loading: boolean;
  resetLoading: boolean;
}>({
  data: {},
  options: [],
  currentOptions: [],
  visible: false,
  loading: false,
  resetLoading: false
});

// gcp 弹窗相关数据
const gcpState = reactive<{
  data: Record<string, any>;
  visible: boolean;
}>({ data: {}, visible: false });

// 计算列表操作列
const tableColumnType = computed(() => {
  const columnType: MerakXTableProps["columnType"] = [
    {
      type: "handle",
      width: language === "zh" ? (!!auth.value?.edit.show ? 220 : 120) : !!auth.value?.edit.show ? 320 : 200,
      slot: "custom-handler"
    }
  ];
  return columnType;
});

// 列表工具条鉴权
const tableToolbar = computed(() => {
  const toolbar: MerakXTableProps["toolbar"] = ["refresh"];
  if (true) {
    toolbar.push("export");
  }
  return toolbar;
});

// 计算弹窗标题
const drawerTitle = computed(() =>
  addState.type === "add"
    ? currentInstance?.proxy?.$t("marking_company.add_company")
    : addState.type === "edit"
      ? addState.data.import_company_name
      : ""
);

// 添加弹窗表单验证
const addFormRules = computed(() => {
  const rules: FormRules = {
    import_company_name: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.import_company_name_valid") }],
    short_name: [
      {
        required: true,
        message: currentInstance?.proxy?.$t("marking_company.short_name_valid")
      },
      {
        trigger: "blur",
        validator: (rule, value, callback) => {
          if (!!value) {
            const params: Record<string, any> = {
              short_name: value
            };
            if (addState.type === "edit") {
              params.import_company_id = addState.data.import_company_id;
            }
            // 重复校验
            validField(params).then(({ code, message }) => {
              if (code == ResultEnum.SUCCESS) {
                callback();
              } else {
                const msg = typeof message === "object" ? Object.values(message)?.[0] : message;
                callback(new Error(msg));
              }
            });
          }
        }
      }
    ]
  };
  if (addState.type === "edit") {
    Object.assign(rules, {
      inn: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.inn_valid") }],
      contract_date: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.contract_date_valid") }],
      contract_number: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.contract_number_valid") }],
      token: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.token_valid") }],
      oms_id: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.oms_id_valid") }],
      contact_person: [{ required: true, message: currentInstance?.proxy?.$t("marking_company.contact_person_valid") }]
    });
  }
  return rules;
});

// 表单工厂字段初始选中项
const factoryDefaultOption = computed<OptionType | undefined>(() => {
  if (!!addState.data.factory_ru_id || typeof addState.data.factory_ru_id === "number") {
    const label = addState.options.find(option => option.value == addState.data.factory_ru_id)?.label ?? "";
    return {
      value: addState.data.factory_ru_id,
      label
    };
  }
  return;
});

// 请求表格头部
const handleQueryColumns: MerakXTableProps["queryColumns"] = async () => {
  return await getTableColumns(Path.markCompany, queueId.value).then(({ code, data }) => {
    if (code == ResultEnum.SUCCESS) {
      tableState.columnsByStore = JSON.parse(JSON.stringify(data.columns));
      return {
        ...data,
        columns: data.columns.map(col => {
          switch (col.field) {
            case "import_company_id":
            case "import_company_name":
            case "short_name":
              col.fixed = "left";
              break;
            case "is_own":
            case "factory_ru_id":
            case "status":
              col.slots = { default: ({ row }) => row[`${col.field}_txt`] };
              break;
            default:
              break;
          }
          return { ...col };
        })
      };
    }
  });
};

// 请求表格数据
const handleQueryData: MerakXTableProps["queryData"] = async ({ page, from }) => {
  const params: Record<string, any> = {};
  if (!!page) {
    Object.assign(params, page);
  }
  if (!!from) {
    Object.assign(params, from);
  }
  return await getTableData(Path.markCompany, params, queueId.value).then(({ code, data }) => {
    if (code == ResultEnum.SUCCESS) {
      return data.table_data;
    }
  });
};

// 处理异步检索下拉
const handleRemoteMethod = (query: string) => {
  addState.currentOptions = !!query
    ? addState.options.filter(option => option.label.toLowerCase().includes(query.toLowerCase()))
    : [];
};

// 保存表单
const handleSave = (reset: boolean = false) => {
  formRef.value
    ?.validate()
    .then(() => {
      confirmWarningMsg({
        msg: `${currentInstance?.proxy?.$t("marking_company.save_message")}${
          addState.type === "add" ? ", " + currentInstance?.proxy?.$t("marking_company.add_message") : ""
        }`,
        callback: (status: string) => {
          if (status === "confirm") {
            if (reset) {
              addState.resetLoading = true;
            } else {
              addState.loading = true;
            }
            saveCompany(addState.data).then(({ code, message }) => {
              if (reset) {
                addState.resetLoading = false;
              } else {
                addState.loading = false;
              }
              if (code == ResultEnum.SUCCESS) {
                saved.value = true;
                if (reset) {
                  formRef.value?.resetFields();
                } else {
                  addState.visible = false;
                }
                ElMessage.success(currentInstance?.proxy?.$t("marking_company.save_success"));
              } else {
                const msg = typeof message === "object" ? Object.values(message)?.[0] : message;
                ElMessage.error(msg);
              }
            });
          }
        }
      });
    })
    .catch(err => {
      const firstKey = Object.keys(err)?.[0];
      formRef.value?.scrollToField(firstKey);
    });
};

// 关闭添加弹窗
const handleCloseAdd = () => {
  if (saved.value) {
    tableRef.value?.reloadData();
    saved.value = false;
  }
};

// 更新列表启用状态
const handleUpdateStatus = (value: boolean, row: Record<string, any>) => {
  confirmWarningMsg({
    msg: value
      ? currentInstance?.proxy?.$t("marking_company.disable_message") ?? ""
      : currentInstance?.proxy?.$t("marking_company.enable_message") ?? "",
    callback: (status: string) => {
      if (status === "confirm") {
        updateStatus({
          import_company_id: row.import_company_id
        }).then(({ code, message }) => {
          if (code == ResultEnum.SUCCESS) {
            tableRef.value?.updateCell({
              rowKey: row.import_company_id,
              field: "status",
              value: value ? 0 : 1,
              text: value
                ? currentInstance?.proxy?.$t("marking_company.disable")
                : currentInstance?.proxy?.$t("marking_company.enable")
            });
          } else {
            const msg = typeof message === "object" ? Object.values(message)?.[0] : message;
            ElMessage.error(msg);
          }
        });
      }
    }
  });
};

nextTick(() => {
  getFactoryOptions().then(({ code, data }) => {
    if (code == ResultEnum.SUCCESS) {
      addState.options = [...(data ?? [])];
    }
  });
  getUserAuth("ApplicantCompany").then(({ code, data }) => {
    if (code == ResultEnum.SUCCESS) {
      auth.value = data;
    }
  });
});
</script>

<style scoped lang="scss">
.merak-table-wrapper .el-button.is-disabled {
  color: var(--el-text-color-disabled) !important;
}
.search_bar_header > * {
  margin-right: var(--merak-space);
  width: 200px;
}

.tag-company-drawer {
  display: flex;
  flex-direction: column;
  height: 100%;
  &-content {
    flex: 1;
    min-height: 0;
    :deep(.el-form-item__content > *) {
      width: 100%;
    }
  }
  &-footer {
    margin-top: var(--merak-space);
    text-align: right;
  }
}
</style>
